package com.ds.esd.util;

import com.alibaba.fastjson.util.TypeUtils;
import com.ds.common.JDSException;
import com.ds.common.util.StringUtility;
import com.ds.config.ErrorListResultModel;
import com.ds.config.ListResultModel;
import com.ds.config.TreeListResultModel;
import com.ds.context.JDSActionContext;
import com.ds.enums.IconEnumstype;
import com.ds.esd.dsm.DSMFactory;
import com.ds.esd.dsm.view.ViewEntityConfig;
import com.ds.esd.custom.CustomViewFactory;
import com.ds.esd.custom.bean.CustomViewBean;
import com.ds.esd.custom.bean.MethodConfig;
import com.ds.esd.custom.enums.CustomMenuItem;
import com.ds.esd.tool.ui.component.list.TreeListItem;
import com.ds.jds.core.esb.util.OgnlUtil;
import com.ds.server.httpproxy.core.HttpRequest;
import com.ds.web.ConstructorBean;
import com.ds.web.RequestParamBean;
import ognl.OgnlContext;

import java.lang.reflect.Constructor;
import java.util.*;

public class TabPageUtil {

    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> getTreeList(Set<K> objs, Class<T> clazz) {
        List<K> result = new ArrayList<K>();
        result.addAll(objs);
        return getTreeList(result, clazz);
    }

    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> getTreeList(List<K> objs, Class<T> clazz) {
        TreeListResultModel<List<T>> userStatusInfo = new TreeListResultModel<List<T>>();
        List<T> pageResult = new ArrayList<T>();
        for (K obj : objs)
            if (obj != null) {
                if (clazz == null || obj.getClass().isAssignableFrom(clazz)) {
                    pageResult.add((T) obj);
                } else {
                    try {
                        T t = (T) fillObj(obj, clazz);
                        pageResult.add(t);
                    } catch (JDSException e) {
                        e.printStackTrace();
                    }
                }
            }
        Object id = JDSActionContext.getActionContext().getParams("id");

        if (id != null && !id.equals("")) {
            String[] orgIdArr = StringUtility.split(id.toString(), ";");
            userStatusInfo.setIds(Arrays.asList(orgIdArr));
        } else {
            if (pageResult.size() > 0) {
                userStatusInfo.setIds(Arrays.asList(new String[]{pageResult.get(0).getId()}));
            }
        }
        userStatusInfo.setData(pageResult);
        return userStatusInfo;
    }


    static <T extends TreeListItem, K extends IconEnumstype> TreeListItem fillObj(K obj, Class<T> clazz) throws JDSException {
        MethodConfig methodConfig = (MethodConfig) JDSActionContext.getActionContext().getContext().get(CustomViewFactory.MethodBeanKey);
        CustomViewBean viewBean = (CustomViewBean) methodConfig.getView();
        Constructor[] constructors = clazz.getDeclaredConstructors();
        T t = null;
        for (Constructor constructor : constructors) {
            Class[] paramClass = constructor.getParameterTypes();
            ConstructorBean constructorBean = new ConstructorBean(constructor);
            if (paramClass.length > 0 && paramClass[0].isAssignableFrom(obj.getClass())) {
                try {
                    Set<Object> objectSet = new LinkedHashSet<>();
                    Set<RequestParamBean> requestParamBeans = constructorBean.getParamSet();
                    for (RequestParamBean paramBean : requestParamBeans) {
                        if (obj.getClass().equals(paramBean.getParamClass()) || paramBean.getParamClass().isAssignableFrom(obj.getClass())) {
                            objectSet.add(obj);
                        } else {
                            Object value = TypeUtils.cast(JDSActionContext.getActionContext().getParams(paramBean.getParamName()), paramBean.getParamClass(), null);
                            objectSet.add(value);
                        }
                    }

                    t = (T) constructor.newInstance(objectSet.toArray());
                    String className = viewBean.getBindService().getName();
                    ViewEntityConfig entityConfig = DSMFactory.getInstance().getViewManager().getViewEntityConfig(className, methodConfig.getDomainId(), methodConfig.getViewInstId());
                    MethodConfig childMethod = entityConfig.getCurrConfig().getMethodByItem(CustomMenuItem.tabEditor);

                    if (childMethod != null) {
                        if (!childMethod.getImageClass().equals(MethodConfig.DefaultImageClass)) {
                            t.setImageClass(childMethod.getImageClass());
                        }
                        t.setClassName(childMethod.getEUClassName());
                    }

                    List<String> hiddenList = viewBean.getHiddenFieldNames();
                    for (String hiddenName : hiddenList) {
                        t.addTagVar(hiddenName, OgnlUtil.getValue(hiddenName, getOgnlContext(), t));
                    }

                    if (viewBean.getCaptionField() != null) {
                        t.setCaption(OgnlUtil.getValue(viewBean.getCaptionField().getFieldname(), getOgnlContext(), t).toString());
                    } else {
                        t.setCaption(obj.getName());
                    }

                    if (viewBean.getUidField() != null) {
                        Object pkValue = OgnlUtil.getValue(viewBean.getUidField().getFieldname(), getOgnlContext(), t);
                        if (pkValue != null) {
                            t.setId(pkValue.toString());
                        }
                    } else {
                        t.setCaption(obj.getType());
                    }
                } catch (Exception e) {
                    e.printStackTrace();
                }

            }
        }

        return t;
    }

    public static OgnlContext getOgnlContext() {
        HttpRequest request = (HttpRequest) JDSActionContext.getActionContext().getHttpRequest();
        return request.getOgnlContext();
    }


    static <T extends TreeListItem, K extends IconEnumstype> List<T> fillObjs(List<K> objs, Class<T> clazz) {
        List<T> result = new ArrayList<T>();
        if (objs != null) {
            for (K obj : objs) {
                if (obj != null) {
                    if (clazz == null || obj.getClass().isAssignableFrom(clazz)) {
                        result.add((T) obj);
                    } else {
                        try {
                            T t = (T) fillObj(obj, clazz);
                            result.add(t);
                        } catch (JDSException e) {
                            e.printStackTrace();
                        }
                    }
                }
            }
        }

        return result;
    }


    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> changTreeList(ListResultModel<List<K>> objs, Class<T> clazz) {
        TreeListResultModel<List<T>> userStatusInfo = new TreeListResultModel<List<T>>();
        try {
            List<T> pageResult = new ArrayList<T>();
            List<K> list = objs.get();
            userStatusInfo.setData(fillObjs(list, clazz));
            userStatusInfo.setSize(objs.getSize());
            Object id = JDSActionContext.getActionContext().getParams("id");
            if (id != null && !id.equals("")) {
                String[] orgIdArr = StringUtility.split(id.toString(), ";");
                userStatusInfo.setIds(Arrays.asList(orgIdArr));
            } else {
                if (pageResult.size() > 0) {
                    userStatusInfo.setIds(Arrays.asList(new String[]{pageResult.get(0).getId()}));
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            userStatusInfo = new ErrorListResultModel();
            ((ErrorListResultModel) userStatusInfo).setErrdes("内部错误");
        }

        return userStatusInfo;
    }


    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> getDefaultTreeList(Set<K> objs, Class<T> clazz) {
        List<K> result = new ArrayList<K>();
        result.addAll(objs);
        return getDefaultTreeList(result, clazz);
    }

    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> getDefaultTreeList(ListResultModel<List<K>> objs, Class<T> clazz) {
        TreeListResultModel<List<T>> userStatusInfo = new TreeListResultModel<List<T>>();
        try {
            List<T> pageResult = new ArrayList<T>();
            List<K> list = objs.get();
            userStatusInfo.setData(fillObjs(list, clazz));
            userStatusInfo.setSize(objs.getSize());
            Object id = JDSActionContext.getActionContext().getParams("id");
            if (id != null && !id.equals("")) {
                String[] orgIdArr = StringUtility.split(id.toString(), ";");
                userStatusInfo.setIds(Arrays.asList(orgIdArr));
            } else {
                if (pageResult.size() > 0) {
                    userStatusInfo.setIds(Arrays.asList(new String[]{pageResult.get(0).getId()}));
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
            userStatusInfo = new ErrorListResultModel();
            ((ErrorListResultModel) userStatusInfo).setErrdes("内部错误");
        }

        return userStatusInfo;
    }


    public static <T extends TreeListItem, K extends IconEnumstype> TreeListResultModel<List<T>> getDefaultTreeList(List<K> objs, Class<T> clazz) {
        TreeListResultModel userStatusInfo = null;
        try {
            userStatusInfo = getTreeList(objs, clazz);
        } catch (Exception e) {
            e.printStackTrace();
            userStatusInfo = new ErrorListResultModel();
            // ((ErrorResultModel) userStatusInfo).setErrcode(e.getErrorCode());
            ((ErrorListResultModel) userStatusInfo).setErrdes("内部错误");
        }

        return userStatusInfo;

    }
}
